package com.tzbank.wisdom.service.impl;

import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.concurrent.Future;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.AsyncResult;
import org.springframework.stereotype.Service;

import com.tzbank.entity.BuriedAction;
import com.tzbank.entity.StandardActionset;
import com.tzbank.entity.StandardRuleset;
import com.tzbank.utils.CodeUtil;
import com.tzbank.utils.ResultUtil;
import com.tzbank.wisdom.dao.BuriedActionMapper;
import com.tzbank.wisdom.dao.StandardActionsetMapper;
import com.tzbank.wisdom.dao.StandardRulesetMapper;
import com.tzbank.wisdom.service.BuriedActionService;

import lombok.extern.slf4j.Slf4j;
import net.sf.json.JSONObject;

@Slf4j
@Service
public class BuriedActionServiceImpl implements BuriedActionService {

	@Autowired
	private StandardActionsetMapper standardActionsetMapper;

	@Autowired
	private BuriedActionMapper buriedActionMapper;

	@Autowired
	private StandardRulesetMapper standardRulesetMapper;

	private void checkRule(BuriedAction buriedAction, JSONObject jsonObject) {
		String ruleIds = buriedAction.getRuleIds();
		if (ruleIds.endsWith(","))
			ruleIds = ruleIds.substring(0, ruleIds.length() - 1);

		ruleIds = "'" + ruleIds.replace(",", "','") + "'";

		final String[] typeArr = {"int", "string"};
		
		Map<String, Boolean> checkMap = new HashMap<String, Boolean>();
		List<StandardRuleset> standardRulesets = this.standardRulesetMapper.selectByRuleId(ruleIds);
		Iterator<StandardRuleset> iterator = standardRulesets.iterator();
		while (iterator.hasNext()) {
			StandardRuleset standardRuleset = iterator.next();
			if (typeArr[0].equals(standardRuleset.getRangeType())) {
				int intVal = jsonObject.getInt(standardRuleset.getRuleFields());
				if (standardRuleset.getOperator().equals(">"))
					checkMap.put(standardRuleset.getRuleFields(), intVal > Integer.parseInt(standardRuleset.getRangeValue()));
				if (standardRuleset.getOperator().equals("<"))
					checkMap.put(standardRuleset.getRuleFields(), intVal < Integer.parseInt(standardRuleset.getRangeValue()));
				if (standardRuleset.getOperator().equals(">="))
					checkMap.put(standardRuleset.getRuleFields(), intVal >= Integer.parseInt(standardRuleset.getRangeValue()));
				if (standardRuleset.getOperator().equals("<="))
					checkMap.put(standardRuleset.getRuleFields(), intVal <= Integer.parseInt(standardRuleset.getRangeValue()));
			}
			if (typeArr[1].equals(standardRuleset.getRangeType())) {
				String strVal = jsonObject.getString(standardRuleset.getRuleFields());
				if (standardRuleset.getOperator().equals("equals"))
					checkMap.put(standardRuleset.getRuleFields(), strVal.equals(standardRuleset.getRangeValue()));
			}
		}

		if (buriedAction.getRuleLogic().equals("&&")) {
			if (buriedAction.getActionFlag() == 0) {
				if (!checkMap.values().contains(false)) {
					// 执行动作
				}
			}
			if (buriedAction.getActionFlag() == 1) {
				if (!checkMap.values().contains(true)) {
					// 执行动作
				}
			}
		}

		if (buriedAction.getRuleLogic().equals("||")) {
			if (buriedAction.getActionFlag() == 0) {
				if (checkMap.values().contains(true)) {
					// 执行动作
				}
			}
			if (buriedAction.getActionFlag() == 1) {
				if (!checkMap.values().contains(false)) {
					// 执行动作
				}
			}
		}

	}

	@Override
	public Future<Map<String, Object>> buriedAction(String url, String iParam, String oParam) {
		// 后端动作
		final String type = "1";

		// 触市时机 01直接调用 02成功调用 03失败调用
		final String[] actionTriggerArr = { "01", "02", "03" };

		// 动作内容
		StandardActionset standardActionset = this.standardActionsetMapper.selectByTypeAndContent(type, url);
		if (null == standardActionset) {
			log.info("动作内容不存在{}", url);
			return new AsyncResult<Map<String, Object>>(ResultUtil.resultMap("动作内容不存在", CodeUtil.CODE_404.getCode(), null));
		}

		// 埋点动作
		BuriedAction buriedAction = this.buriedActionMapper.selectByBusinessActionId(standardActionset.getActionId());
		if (null == buriedAction) {
			log.info("埋点动作不存在{}", url);
			return new AsyncResult<Map<String, Object>>(ResultUtil.resultMap("埋点动作不存在", CodeUtil.CODE_404.getCode(), null));
		}
		JSONObject oParamJson = JSONObject.fromObject(oParam);
		JSONObject iParamJson = JSONObject.fromObject(iParam);

		// 直接调用
		if (actionTriggerArr[0].equals(buriedAction.getActionTrigger())) {
			this.checkRule(buriedAction, iParamJson);
			return new AsyncResult<Map<String, Object>>(ResultUtil.resultMap("直接调用", CodeUtil.CODE_200.getCode(), null));
		}

		// 成功调用
		if (actionTriggerArr[1].equals(buriedAction.getActionTrigger())) {
			if (CodeUtil.CODE_200.getCode().equals(oParamJson.getString("code"))) {
				this.checkRule(buriedAction, iParamJson);
				return new AsyncResult<Map<String, Object>>(ResultUtil.resultMap("成功调用", CodeUtil.CODE_200.getCode(), null));
			}
		}

		// 失败调用
		if (actionTriggerArr[2].equals(buriedAction.getActionTrigger())) {
			if (!CodeUtil.CODE_200.getCode().equals(oParamJson.getString("code"))) {
				this.checkRule(buriedAction, iParamJson);
				return new AsyncResult<Map<String, Object>>(ResultUtil.resultMap("失败调用", CodeUtil.CODE_200.getCode(), null));
			}
		}

		return new AsyncResult<Map<String, Object>>(ResultUtil.resultMap("触发时机不存在" + buriedAction.getActionTrigger(), CodeUtil.CODE_404.getCode(), null));

	}

}
